#ifndef DEF_H
#define DEF_H

#include <assert.h>
#include <errno.h>
#include <stdbool.h>
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <string.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_ttf.h>
#include <SDL2/SDL_image.h>

#define DEBUG 0

#define WINDOW_TITLE "cmus-remote-graphical-sdl-c"
#define WINDOW_W 300
#define WINDOW_H 300

#define BORDER_W 20
#define BORDER_H 20

#define FIELD_W (WINDOW_W - BORDER_W * 2)
#define FIELD_H (WINDOW_H - BORDER_H * 2)

#define FONTSIZE 20
#define FONTHEIGHT ((int) ((float)FONTSIZE * 1.5))

#define WHITE 0xffffffff
#define BLACK 0x000000ff

#define BG 0x100410ff
#define FG 0xff87ffff

#define BUTTON_TOGGLE_STATUS 'a'
#define BUTTON_NEXT          'b'
#define BUTTON_PREV          'c'

typedef struct {
    char id;
    unsigned int x;
    unsigned int y;
    unsigned int w;
    unsigned int h;
    void (*callback)(void* data);
    SDL_Texture *texture;
} button;

/* using a simple linked list for buttons */
typedef struct node {
    button payload;
    struct node *next;
} button_node;

typedef struct {
    uint64_t duration;
    char *file;
    char *album_tag;
    char *albumartist_tag;
    char *artist_tag;
    char *comment_tag;
    char *date_tag;
    char *genre_tag;
    char *title_tag;
    uint64_t discnumber_tag;
    uint64_t tracknumber_tag;
} track;

typedef struct {
    char *aaa_mode;
    char *status;
    uint64_t vol_left;
    uint64_t vol_right;
    uint64_t position;
    bool repeat;
    bool repeat_current;
    bool shuffle;
} player;

/* stores indices for various fields that can cause events */
/* to happen, used to encode udpate information */
typedef enum {
    TOKEN_DURATION = 0, TOKEN_FILE, TOKEN_ALBUM_TAG, TOKEN_ALBUMARTIST_TAG,
    TOKEN_ARTIST_TAG, TOKEN_COMMENT_TAG, TOKEN_DATE_TAG, TOKEN_GENRE_TAG,
    TOKEN_TITLE_TAG, TOKEN_DISCNUMBER_TAG, TOKEN_TRACKNUMBER_TAG,
    TOKEN_AAA_MODE, TOKEN_STATUS, TOKEN_VOL_LEFT, TOKEN_VOL_RIGHT,
    TOKEN_POSITION, TOKEN_REPEAT, TOKEN_REPEAT_CURRENT, TOKEN_SHUFFLE,
    /* delimits all the tokens for iteration */
    TOKEN_ENUM_SIZE
} token;

/* stores miscellaneous state information */
typedef struct {
    /* commands dynamic renderer updates */
    bool render_change;
    /* stores whether last parse token was completely parsed */
    bool incomplete_parse;
    /* commands dynamic album art changes */
    bool file_changed;

    /* stores last frame */
    int frame;

    /* cmus state hash */
    uint64_t previous_info_hash;

    /* points to the active window */
    SDL_Window *window;
    /* points to the active renderer */
    SDL_Renderer *renderer;
    /* points to the active display */
    SDL_Texture *display;
    /* points to the active ttf_font */
    TTF_Font *font;

    /* points to the root node of the button linked list*/
    button_node *root;
    /* points to the tail node of the button linked list*/
    button_node *tail;

    /* stores the current track */
    track *cr_track;
    /* stores the current player */
    player *cr_player;

    /*  */
} cr_state;

#endif